<template>
  <div class="teacher-center">
    <div class="fullscreen-bg" aria-hidden="true"></div>

    <header class="page-header">
      <div class="header-left">
        <h2>老师端中心</h2>
        <p class="subtitle"><span class="welcome">欢迎，{{ teacherDisplayName }},</span>管理任务与教学环境资源</p>
      </div>
      <div class="page-actions">
        <a-button danger @click="handleLogout">退出</a-button>
      </div>
    </header>

    <a-tabs v-model:activeKey="activeTab" class="tabs">
      <a-tab-pane key="tasks" tab="任务">
        <div class="toolbar">
          <a-space wrap>
            <a-input v-model:value="taskQuery.title" allow-clear placeholder="任务标题" style="width: 200px" />
            <a-select v-model:value="taskQuery.type" allow-clear placeholder="任务类型" style="width: 140px">
              <a-select-option value="coding">编程练习</a-select-option>
              <a-select-option value="quiz">知识测验</a-select-option>
              <a-select-option value="project">项目作业</a-select-option>
              <a-select-option value="reading">阅读任务</a-select-option>
            </a-select>
            <a-select v-model:value="taskQuery.status" allow-clear placeholder="任务状态" style="width: 140px">
              <a-select-option value="pending">待发布</a-select-option>
              <a-select-option value="in-progress">进行中</a-select-option>
              <a-select-option value="completed">已完成</a-select-option>
            </a-select>
            <a-button type="primary" @click="handleSearchTasks">查询</a-button>
            <a-button @click="handleResetTasks">重置</a-button>
            <a-button type="primary" @click="openCreateTask">新建任务</a-button>
          </a-space>
        </div>

        <template v-if="tasks.length">
          <a-table :data-source="tasks" :row-key="row => row.id" :pagination="false">
            <a-table-column title="#" :customRender="({ index }) => index + 1" width="60" />
            <a-table-column title="标题" dataIndex="title" />
            <a-table-column title="类型" dataIndex="type">
              <template #default="{ record }">
                {{ typeLabel(record.type) }}
              </template>
            </a-table-column>
            <a-table-column title="难度" dataIndex="difficulty">
              <template #default="{ record }">
                {{ difficultyLabel(record.difficulty) }}
              </template>
            </a-table-column>
            <a-table-column title="状态" dataIndex="status">
              <template #default="{ record }">
                <a-tag :color="statusTagColor(record.status)">{{ statusLabel(record.status) }}</a-tag>
              </template>
            </a-table-column>
            <a-table-column title="截止时间" dataIndex="deadline">
              <template #default="{ record }">
                {{ formatDate(record.deadline) }}
              </template>
            </a-table-column>
            <a-table-column title="预计用时" dataIndex="estimatedTime">
              <template #default="{ record }">
                {{ record.estimatedTime }} 分钟
              </template>
            </a-table-column>
            <a-table-column title="描述" dataIndex="description" ellipsis />
            <a-table-column title="操作" width="200">
              <template #default="{ record }">
                <a-space>
                  <a-button size="small" @click="openEditTask(record)">编辑</a-button>
                  <a-button size="small" danger @click="confirmDeleteTask(record)">删除</a-button>
                </a-space>
              </template>
            </a-table-column>
          </a-table>
          <div style="margin-top: 12px; text-align: right;">
            <a-pagination
              :current="taskPagination.pageNum"
              :pageSize="taskPagination.pageSize"
              :total="taskPagination.total"
              show-size-changer
              :page-size-options="['10','20','50']"
              @change="handleTaskPageChange"
              @showSizeChange="handleTaskPageSizeChange"
            />
          </div>
        </template>
        <a-empty v-else description="暂无任务" />

        <!-- Antd Modal 替换 Element Dialog 与 Form -->
        <a-modal v-model:open="createTaskVisible" title="新建并发布任务" :width="560">
          <a-form ref="taskFormRef" :model="taskForm" :rules="taskRules" :label-col="{ style: { width: '100px' } }">
            <a-form-item label="标题" name="title">
              <a-input v-model:value="taskForm.title" placeholder="请输入任务标题" />
            </a-form-item>
            <a-form-item label="类型" name="type">
              <a-select v-model:value="taskForm.type" placeholder="请选择类型">
                <a-select-option value="coding">编程练习</a-select-option>
                <a-select-option value="quiz">知识测验</a-select-option>
                <a-select-option value="project">项目作业</a-select-option>
                <a-select-option value="reading">阅读任务</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="难度" name="difficulty">
              <a-select v-model:value="taskForm.difficulty" placeholder="请选择难度">
                <a-select-option value="easy">简单</a-select-option>
                <a-select-option value="medium">中等</a-select-option>
                <a-select-option value="hard">困难</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="截止时间" name="deadline">
              <a-date-picker v-model:value="taskForm.deadline" value-format="YYYY-MM-DD" format="YYYY-MM-DD" />
            </a-form-item>
            <a-form-item label="预计用时" name="estimatedTime">
              <a-input-number v-model:value="taskForm.estimatedTime" :min="1" :max="600" />
            </a-form-item>
            <a-form-item label="描述" name="description">
              <a-textarea v-model:value="taskForm.description" :rows="3" placeholder="任务描述" />
            </a-form-item>
          </a-form>
          <template #footer>
            <a-button @click="createTaskVisible = false">取消</a-button>
            <a-button type="primary" @click="submitCreateTask">发布任务</a-button>
          </template>
        </a-modal>

        <!-- 编辑任务模态框 -->
        <a-modal v-model:open="editTaskVisible" title="编辑任务" :width="560">
          <a-form ref="editTaskFormRef" :model="editTaskForm" :rules="taskRules" :label-col="{ style: { width: '100px' } }">
            <a-form-item label="标题" name="title">
              <a-input v-model:value="editTaskForm.title" placeholder="请输入任务标题" />
            </a-form-item>
            <a-form-item label="类型" name="type">
              <a-select v-model:value="editTaskForm.type" placeholder="请选择类型">
                <a-select-option value="coding">编程练习</a-select-option>
                <a-select-option value="quiz">知识测验</a-select-option>
                <a-select-option value="project">项目作业</a-select-option>
                <a-select-option value="reading">阅读任务</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="难度" name="difficulty">
              <a-select v-model:value="editTaskForm.difficulty" placeholder="请选择难度">
                <a-select-option value="easy">简单</a-select-option>
                <a-select-option value="medium">中等</a-select-option>
                <a-select-option value="hard">困难</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="截止时间" name="deadline">
              <a-date-picker v-model:value="editTaskForm.deadline" value-format="YYYY-MM-DD" format="YYYY-MM-DD" />
            </a-form-item>
            <a-form-item label="预计用时" name="estimatedTime">
              <a-input-number v-model:value="editTaskForm.estimatedTime" :min="1" :max="600" />
            </a-form-item>
            <a-form-item label="描述" name="description">
              <a-textarea v-model:value="editTaskForm.description" :rows="3" placeholder="任务描述" />
            </a-form-item>
          </a-form>
          <template #footer>
            <a-button @click="editTaskVisible = false">取消</a-button>
            <a-button type="primary" @click="submitEditTask">保存修改</a-button>
          </template>
        </a-modal>
      </a-tab-pane>

      <a-tab-pane key="students" tab="学生">
        <div class="filter-row">
          <a-space wrap>
            <a-input v-model:value="studentQuery.realName" allow-clear placeholder="姓名" style="width: 160px" />
            <a-input v-model:value="studentQuery.studentNo" allow-clear placeholder="学号" style="width: 160px" />
            <a-input v-model:value="studentQuery.schoolName" allow-clear placeholder="学校" style="width: 180px" />
            <a-input v-model:value="studentQuery.collegeName" allow-clear placeholder="学院" style="width: 180px" />
            <a-input v-model:value="studentQuery.majorName" allow-clear placeholder="专业" style="width: 180px" />
            <a-input v-model:value="studentQuery.className" allow-clear placeholder="班级" style="width: 160px" />
            <a-input v-model:value="studentQuery.grade" allow-clear placeholder="年级（如2021级）" style="width: 160px" />
            <a-button type="primary" @click="handleSearchStudents">查询</a-button>
            <a-button @click="handleResetStudents">重置</a-button>
            <a-button type="primary" @click="openCreateStudent">新增学生</a-button>
          </a-space>
        </div>

        <template v-if="students.length">
          <a-table :data-source="students" :row-key="row => row.userId || row.id" :pagination="false">
            <a-table-column title="#" :customRender="({ index }) => index + 1" width="60" />
            <a-table-column title="学号" dataIndex="studentNo" />
            <a-table-column title="姓名" dataIndex="realName" />
            <!-- <a-table-column title="邮箱" dataIndex="email" /> -->
            <a-table-column title="手机号" dataIndex="phone" />
            <a-table-column title="学校" dataIndex="schoolName" />
            <a-table-column title="学院" dataIndex="collegeName" />
            <a-table-column title="专业" dataIndex="majorName" />
            <a-table-column title="班级" dataIndex="className" />
            <a-table-column title="年级" dataIndex="grade" />
            <a-table-column title="操作" width="200">
              <template #default="{ record }">
                <a-space>
                  <a-button size="small" @click="openEditStudent(record)">编辑</a-button>
                  <a-button size="small" danger @click="confirmDeleteStudent(record)">删除</a-button>
                </a-space>
              </template>
            </a-table-column>
          </a-table>
          <div style="margin-top: 12px; text-align: right;">
            <a-pagination
              :current="studentPagination.pageNum"
              :pageSize="studentPagination.pageSize"
              :total="studentPagination.total"
              show-size-changer
              :page-size-options="['10','20','50']"
              @change="handleStudentPageChange"
              @showSizeChange="handleStudentPageSizeChange"
            />
          </div>
        </template>
        <a-empty v-else description="暂无学生" />

        <a-modal v-model:open="createStudentVisible" title="新增学生" :width="720">
          <a-form ref="createStudentFormRef" :model="createStudentForm" :rules="studentRules" :label-col="{ style: { width: '100px' } }">
            <a-form-item label="账号" name="username">
              <a-input v-model:value="createStudentForm.username" placeholder="用于登录的账号（可与学号相同）" />
            </a-form-item>
            <a-form-item label="学号" name="studentNo">
              <a-input v-model:value="createStudentForm.studentNo" placeholder="请输入学号" />
            </a-form-item>
            <a-form-item label="姓名" name="realName">
              <a-input v-model:value="createStudentForm.realName" placeholder="请输入姓名" />
            </a-form-item>
            <a-form-item label="性别" name="gender">
              <a-select v-model:value="createStudentForm.gender" placeholder="请选择">
                <a-select-option value="M">男</a-select-option>
                <a-select-option value="F">女</a-select-option>
                <a-select-option value="other">其他</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="邮箱" name="email">
              <a-input v-model:value="createStudentForm.email" placeholder="name@example.com（可选）" />
            </a-form-item>
            <a-form-item label="手机号" name="phone">
              <a-input v-model:value="createStudentForm.phone" placeholder="联系电话（可选）" />
            </a-form-item>
            <a-form-item label="学校" name="schoolName">
              <a-input v-model:value="createStudentForm.schoolName" placeholder="学校名称" />
            </a-form-item>
            <a-form-item label="学院" name="collegeName">
              <a-input v-model:value="createStudentForm.collegeName" placeholder="学院名称" />
            </a-form-item>
            <a-form-item label="专业" name="majorName">
              <a-input v-model:value="createStudentForm.majorName" placeholder="专业名称" />
            </a-form-item>
            <a-form-item label="班级" name="className">
              <a-input v-model:value="createStudentForm.className" placeholder="例如：计科2021-1班" />
            </a-form-item>
            <a-form-item label="年级" name="grade">
              <a-input v-model:value="createStudentForm.grade" placeholder="例如：2021级" />
            </a-form-item>
            <a-form-item label="头像URL" name="avatarUrl">
              <a-input v-model:value="createStudentForm.avatarUrl" placeholder="https://...（可选）" />
            </a-form-item>
          </a-form>
          <template #footer>
            <a-button @click="createStudentVisible = false">取消</a-button>
            <a-button type="primary" @click="submitCreateStudent">创建</a-button>
          </template>
        </a-modal>

        <a-modal v-model:open="editStudentVisible" title="编辑学生" :width="720">
          <a-form ref="editStudentFormRef" :model="editStudentForm" :rules="studentRules" :label-col="{ style: { width: '100px' } }">
            <a-form-item label="账号" name="username">
              <a-input v-model:value="editStudentForm.username" placeholder="请输入账号" />
            </a-form-item>
            <a-form-item label="学号" name="studentNo">
              <a-input v-model:value="editStudentForm.studentNo" placeholder="请输入学号" />
            </a-form-item>
            <a-form-item label="姓名" name="realName">
              <a-input v-model:value="editStudentForm.realName" placeholder="请输入姓名" />
            </a-form-item>
            <a-form-item label="性别" name="gender">
              <a-select v-model:value="editStudentForm.gender" placeholder="请选择">
                <a-select-option value="male">男</a-select-option>
                <a-select-option value="female">女</a-select-option>
                <a-select-option value="other">其他</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="邮箱" name="email">
              <a-input v-model:value="editStudentForm.email" placeholder="name@example.com" />
            </a-form-item>
            <a-form-item label="手机号" name="phone">
              <a-input v-model:value="editStudentForm.phone" placeholder="联系电话" />
            </a-form-item>
            <a-form-item label="学校" name="schoolName">
              <a-input v-model:value="editStudentForm.schoolName" placeholder="学校名称" />
            </a-form-item>
            <a-form-item label="学院" name="collegeName">
              <a-input v-model:value="editStudentForm.collegeName" placeholder="学院名称" />
            </a-form-item>
            <a-form-item label="专业" name="majorName">
              <a-input v-model:value="editStudentForm.majorName" placeholder="专业名称" />
            </a-form-item>
            <a-form-item label="班级" name="className">
              <a-input v-model:value="editStudentForm.className" placeholder="例如：计科2021-1班" />
            </a-form-item>
            <a-form-item label="年级" name="grade">
              <a-input v-model:value="editStudentForm.grade" placeholder="例如：2021级" />
            </a-form-item>
            <a-form-item label="头像URL" name="avatarUrl">
              <a-input v-model:value="editStudentForm.avatarUrl" placeholder="https://...（可选）" />
            </a-form-item>
          </a-form>
          <template #footer>
            <a-button @click="editStudentVisible = false">取消</a-button>
            <a-button type="primary" @click="submitEditStudent">保存</a-button>
          </template>
        </a-modal>
      </a-tab-pane>

      <a-tab-pane key="envs" tab="环境搭建">
        <div class="toolbar">
          <a-space>
            <a-input v-model:value="envQuery.groupId" allow-clear placeholder="班级/分组ID" style="width: 180px" />
            <a-select v-model:value="envQuery.type" allow-clear placeholder="类型" style="width: 140px">
              <a-select-option value="IDE">IDE</a-select-option>
              <a-select-option value="JUPYTER">Jupyter</a-select-option>
              <a-select-option value="MYSQL">MySQL</a-select-option>
            </a-select>
            <a-select v-model:value="envQuery.status" allow-clear placeholder="状态" style="width: 140px">
              <a-select-option value="CREATING">创建中</a-select-option>
              <a-select-option value="RUNNING">运行中</a-select-option>
              <a-select-option value="STOPPED">已停止</a-select-option>
              <a-select-option value="ERROR">异常</a-select-option>
            </a-select>
            <a-button type="primary" @click="() => { envPage.pageNum = 1; loadEnvs() }">查询</a-button>
            <a-button @click="() => { Object.assign(envQuery, { type: '', status: '', groupId: '' }); envPage.pageNum = 1; loadEnvs() }">重置</a-button>
            <a-button type="primary" @click="openCreateEnv">新建环境资源</a-button>
          </a-space>
        </div>

        <div v-if="envs.length" class="card-grid">
          <div v-for="env in envs" :key="env.environmentId" class="card">
            <div class="card-header">
              <div class="title">{{ env.name }}</div>
              <a-tag :color="envTagColor(env.status)">{{ envStatusLabel(env.status) }}</a-tag>
            </div>
            <div class="card-content">
              <div class="meta">
                <div class="meta-item"><span>类型</span><strong>{{ env.type }}</strong></div>
                <div class="meta-item" v-if="env.baseUrl"><span>入口</span><strong class="monospace">{{ env.baseUrl }}</strong></div>
                <div class="meta-item" v-if="env.groupId"><span>班级/组</span><strong>{{ env.groupId }}</strong></div>
              </div>
              <div class="desc">{{ env.description }}</div>
              <div style="margin-top:10px; text-align:right;">
                <a-space>
                  <a-button size="small" @click="openManageUsages(env)">学生访问</a-button>
                  <a-button size="small" danger @click="confirmRemoveEnv(env)">删除</a-button>
                </a-space>
              </div>
            </div>
          </div>
        </div>
        <a-empty v-else description="暂无环境资源" />

        <div style="margin-top: 12px; text-align: right;">
          <a-pagination
            :current="envPage.pageNum"
            :pageSize="envPage.pageSize"
            :total="envPage.total"
            show-size-changer
            :page-size-options="['10','20','50']"
            @change="(p,s)=>{ envPage.pageNum=p; envPage.pageSize=s; loadEnvs() }"
            @showSizeChange="(p,s)=>{ envPage.pageNum=1; envPage.pageSize=s; loadEnvs() }"
          />
        </div>

        <a-modal v-model:open="createEnvVisible" title="新建环境资源" :width="560">
          <a-form ref="envFormRef" :model="envForm" :rules="envRules" :label-col="{ style: { width: '100px' } }">
            <a-form-item label="名称" name="name">
              <a-input v-model:value="envForm.name" placeholder="请输入资源名称" />
            </a-form-item>
            <a-form-item label="类型" name="type">
              <a-select v-model:value="envForm.type" placeholder="请选择类型">
                <a-select-option value="IDE">IDE</a-select-option>
                <a-select-option value="JUPYTER_HUB">JUPYTER_HUB</a-select-option>
                <a-select-option value="MYSQL">MYSQL</a-select-option>
              </a-select>
            </a-form-item>
            <a-form-item label="班级/组ID" name="groupId">
              <a-input v-model:value="envForm.groupId" placeholder="如：class-2021-1" />
            </a-form-item>
            <a-form-item label="描述" name="description">
              <a-textarea v-model:value="envForm.description" :rows="3" placeholder="资源说明" />
            </a-form-item>
          </a-form>
          <template #footer>
            <a-button @click="createEnvVisible = false">取消</a-button>
            <a-button type="primary" @click="submitCreateEnv">创建资源</a-button>
          </template>
        </a-modal>

        <!-- 学生访问管理对话框 -->
        <a-modal v-model:open="usageVisible" title="学生访问管理" :width="900">
          <div v-if="currentEnv">
            <p><strong>{{ currentEnv.name }}</strong>（{{ currentEnv.type }}） - 状态：{{ envStatusLabel(currentEnv.status) }}</p>
            <div class="filter-row">
              <a-space wrap>
                <a-select
                  v-model:value="studentPicker.selected"
                  mode="multiple"
                  show-search
                  :filter-option="false"
                  :options="studentPicker.options"
                  :loading="studentPicker.loading"
                  placeholder="选择学生（可输入学号/姓名搜索，多选）"
                  style="min-width: 520px"
                  @search="remoteSearchStudents"
                />
                <a-button 
                  type="primary" 
                  :loading="usageLoading.addingStudents"
                  @click="addSelectedStudents"
                >
                  {{ usageLoading.addingStudents ? '添加中...' : '添加选中' }}
                </a-button>
              </a-space>
            </div>
            <div class="filter-row">
              <a-space wrap>
                <a-select
                  v-model:value="classPicker.major"
                  show-search
                  :filter-option="false"
                  :options="classPicker.optionsMajor"
                  :loading="classPicker.loadingMajor"
                  placeholder="选择专业（输入搜索）"
                  style="width: 220px"
                  @search="remoteSearchMajor"
                  @change="onMajorChange"
                />
                <a-select
                  v-model:value="classPicker.className"
                  show-search
                  :filter-option="false"
                  :options="classPicker.optionsClass"
                  :loading="classPicker.loadingClass"
                  placeholder="选择班级（输入搜索）"
                  style="width: 220px"
                  @search="remoteSearchClass"
                />
                <a-button 
                  type="primary" 
                  :loading="usageLoading.addingClassStudents"
                  @click="addClassStudents"
                >
                  {{ usageLoading.addingClassStudents ? '添加中...' : '添加该班级全部学生' }}
                </a-button>
              </a-space>
            </div>
            <!-- <div class="filter-row">
              <a-textarea v-model:value="batchInput" :rows="3" placeholder="批量添加：每行一个，格式 学号[,姓名]" />
              <div style="text-align:right;margin-top:8px;">
                <a-button @click="batchInput=''">清空</a-button>
                <a-button type="primary" @click="addBatchUsages" style="margin-left:8px;">批量添加</a-button>
              </div>
            </div> -->
            <a-table 
              :data-source="currentUsages" 
              :row-key="row=>row.id" 
              :pagination="usagePagination" 
              size="small"
              :loading="usageLoading.refreshing"
            >
              <a-table-column title="#" :customRender="({index})=>index+1" width="50" />
              <a-table-column title="学号" dataIndex="studentNo" />
              <a-table-column title="姓名" dataIndex="displayName" />
              <a-table-column title="访问入口" dataIndex="accessUrl" />
              <a-table-column title="用户名" dataIndex="dbUsername" v-if="currentEnv.type === 'MYSQL'" />
              <a-table-column title="密码" dataIndex="dbPassword" v-if="currentEnv.type === 'MYSQL'" />
              <a-table-column title="数据库名" dataIndex="dbName" v-if="currentEnv.type === 'MYSQL'" />
              <a-table-column title="端口" dataIndex="allocatedPort" v-if="currentEnv.type === 'MYSQL'" />
              <a-table-column title="JupyterHub用户名" dataIndex="accessUsername" v-if="currentEnv.type === 'JUPYTERHUB'" />
              <a-table-column title="JupyterHub密码" dataIndex="accessPassword" v-if="currentEnv.type === 'JUPYTERHUB'" />
              <a-table-column title="操作" width="140">
                <template #default="{ record }">
                  <a-space>
                    <a-button size="small" danger @click="confirmRemoveUsage(record)">移除</a-button>
                  </a-space>
                </template>
              </a-table-column>
            </a-table>
          </div>
          <template #footer>
            <a-space>
              <a-button @click="usageVisible=false">关闭</a-button>
            </a-space>
          </template>
        </a-modal>
      </a-tab-pane>
    </a-tabs>
  </div>
  
 </template>

<script setup>
import { ref, reactive, onMounted, h } from 'vue'
import { useRouter } from 'vue-router'
import { getAuth } from '../utils/auth'
import { message, Modal } from 'ant-design-vue'
import { logout as doLogout } from '../utils/auth'
import { fetchTasks, fetchEnvs } from '../api/teacher'
import { pageTasks, createTaskApi, updateTaskApi, deleteTaskApi } from '../api/task'
import { pageTeacherEnvs, createTeacherEnv, listUsages, bindUsages, deleteTeacherEnv, deleteUsage } from '../api/teacherEnvs'
import { pageStudents as pageStudentsApi, listStudentMajors, listStudentClasses, createRandomUser, updateUser, deleteUser } from '../api/users'

const activeTab = ref('tasks')
const teacherDisplayName = (getAuth()?.username) || '老师'
const router = useRouter()

// 任务列表
const tasks = ref([])
const taskPagination = reactive({ pageNum: 1, pageSize: 10, total: 0 })
const taskQuery = reactive({ title: '', type: '', status: '' })

// 新建任务
const createTaskVisible = ref(false)
const taskFormRef = ref()
const taskForm = reactive({
  title: '',
  type: '',
  difficulty: '',
  deadline: '',
  estimatedTime: 30,
  description: ''
})

// 编辑任务
const editTaskVisible = ref(false)
const editTaskFormRef = ref()
const editTaskForm = reactive({
  id: '',
  title: '',
  type: '',
  difficulty: '',
  deadline: '',
  estimatedTime: 30,
  description: ''
})
const taskRules = {
  title: [{ required: true, message: '请输入标题', trigger: 'blur' }],
  type: [{ required: true, message: '请选择类型', trigger: 'change' }],
  difficulty: [{ required: true, message: '请选择难度', trigger: 'change' }],
  deadline: [{ required: true, message: '请选择截止日期', trigger: 'change' }],
  estimatedTime: [{ type: 'number', required: true, message: '请输入用时', trigger: 'change' }]
}
const openCreateTask = () => {
  createTaskVisible.value = true
}

const openEditTask = (task) => {
  editTaskForm.id = task.id
  editTaskForm.title = task.title
  editTaskForm.type = task.type
  editTaskForm.difficulty = task.difficulty
  editTaskForm.deadline = task.deadline
  editTaskForm.estimatedTime = task.estimatedTime
  editTaskForm.description = task.description
  editTaskVisible.value = true
}

const resetTaskForm = () => {
  taskForm.title = ''
  taskForm.type = ''
  taskForm.difficulty = ''
  taskForm.deadline = ''
  taskForm.estimatedTime = 30
  taskForm.description = ''
}

const resetEditTaskForm = () => {
  editTaskForm.id = ''
  editTaskForm.title = ''
  editTaskForm.type = ''
  editTaskForm.difficulty = ''
  editTaskForm.deadline = ''
  editTaskForm.estimatedTime = 30
  editTaskForm.description = ''
}
const submitCreateTask = async () => {
  try {
    await taskFormRef.value?.validate()
    const payload = { ...taskForm, status: 'published' }
    await createTaskApi(payload)
    message.success('任务已发布给学生')
    createTaskVisible.value = false
    resetTaskForm()
    // 重置到第一页并刷新
    taskPagination.pageNum = 1
    await loadTasks()
  } catch (_) {}
}

const submitEditTask = async () => {
  try {
    await editTaskFormRef.value?.validate()
    const payload = { ...editTaskForm }
    await updateTaskApi(editTaskForm.id, payload)
    message.success('任务修改成功')
    editTaskVisible.value = false
    resetEditTaskForm()
    await loadTasks()
  } catch (_) {}
}

async function confirmDeleteTask (task) {
  try {
    Modal.confirm({
      title: '删除任务确认',
      content: `确定要删除任务"${task.title}"吗？\n\n删除后学生将无法看到此任务，且无法恢复。`,
      okText: '确认删除',
      okType: 'danger',
      cancelText: '取消',
      onOk: async () => {
        try {
          // 显示删除进度
          message.loading('正在删除任务...', 0)
          
          await deleteTaskApi(task.id)
          
          // 关闭加载提示
          message.destroy()
          
          message.success('任务删除成功')
          // 如果当前页没有数据了，回到上一页
          if (tasks.value.length === 1 && taskPagination.pageNum > 1) {
            taskPagination.pageNum--
          }
          await loadTasks()
        } catch (error) {
          // 关闭加载提示
          message.destroy()
          
          console.error('删除任务失败:', error)
          message.error('删除任务失败，请重试')
        }
      }
    })
  } catch (error) {
    console.error('显示确认对话框失败:', error)
    message.error('操作失败，请重试')
  }
}

// 环境资源（老师端真实数据）
const envs = ref([])
const envPage = reactive({ pageNum: 1, pageSize: 10, total: 0 })
const envQuery = reactive({ type: '', status: '', groupId: '' })

const createEnvVisible = ref(false)
const envFormRef = ref()
const envForm = reactive({ name: '', type: '', description: '', groupId: '' })
const envRules = {
  name: [{ required: true, message: '请输入资源名称', trigger: 'blur' }],
  type: [{ required: true, message: '请选择类型', trigger: 'change' }]
}
const openCreateEnv = () => {
  createEnvVisible.value = true
}
const resetEnvForm = () => {
  envForm.name = ''
  envForm.type = ''
  envForm.groupId = ''
  envForm.description = ''
}
const submitCreateEnv = async () => {
  try {
    await envFormRef.value?.validate()
    const payload = { ...envForm, status: 'CREATING' }
    await createTeacherEnv(payload)
    message.success('环境资源已创建，正在准备中')
    createEnvVisible.value = false
    resetEnvForm()
    await loadEnvs()
  } catch (_) {}
}

// 学生
const students = ref([])
const studentPagination = reactive({ pageNum: 1, pageSize: 10, total: 0 })
const studentQuery = reactive({ schoolName: '', collegeName: '', majorName: '', className: '', grade: '', studentNo: '', realName: '' })
const studentColumns = [
  { title: '#', dataIndex: 'index', key: 'index', width: 60 },
  { title: '账号', dataIndex: 'username', key: 'username' },
  { title: '姓名', dataIndex: 'name', key: 'name' },
  { title: '邮箱', dataIndex: 'email', key: 'email' },
  { title: '班级', dataIndex: 'className', key: 'className' },
  { title: '操作', key: 'actions', width: 200 }
]
const createStudentVisible = ref(false)
const editStudentVisible = ref(false)
const createStudentFormRef = ref()
const editStudentFormRef = ref()
const createStudentForm = reactive({
  username: '', studentNo: '', realName: '', gender: '', email: '', phone: '',
  schoolName: '', collegeName: '', majorName: '', className: '', grade: '', avatarUrl: ''
})
const editStudentForm = reactive({
  userId: '', username: '', studentNo: '', realName: '', gender: '', email: '', phone: '',
  schoolName: '', collegeName: '', majorName: '', className: '', grade: '', avatarUrl: ''
})
const studentRules = {
  username: [{ required: true, message: '请输入账号', trigger: 'blur' }],
  realName: [{ required: true, message: '请输入姓名', trigger: 'blur' }],
  email: [{ type: 'email', required: false, message: '邮箱格式不正确', trigger: 'blur' }]
}
const handleSearchStudents = () => {
  studentPagination.pageNum = 1
  loadStudents()
}
const handleResetStudents = () => {
  Object.assign(studentQuery, { schoolName: '', collegeName: '', majorName: '', className: '', grade: '', studentNo: '', realName: '' })
  studentPagination.pageNum = 1
  loadStudents()
}

function scrollStudentsTop () {
  try {
    // 优先滚动容器顶部
    const pane = document.querySelector('.tabs :is(.ant-tabs-content-holder, .el-tabs__content)')
    if (pane) pane.scrollTo({ top: 0, behavior: 'smooth' })
    // 再兜底窗口滚动
    window.scrollTo({ top: 0, behavior: 'smooth' })
  } catch (_) {}
}

const handleStudentPageChange = (p, s) => {
  studentPagination.pageNum = p
  studentPagination.pageSize = s
  loadStudents().then(scrollStudentsTop)
}

const handleStudentPageSizeChange = (p, s) => {
  studentPagination.pageNum = 1
  studentPagination.pageSize = s
  loadStudents().then(scrollStudentsTop)
}

// 任务分页处理函数
const handleTaskPageChange = (p, s) => {
  taskPagination.pageNum = p
  taskPagination.pageSize = s
  loadTasks()
}

const handleTaskPageSizeChange = (p, s) => {
  taskPagination.pageNum = 1
  taskPagination.pageSize = s
  loadTasks()
}

// 任务搜索和重置处理函数
const handleSearchTasks = () => {
  taskPagination.pageNum = 1
  loadTasks()
}

const handleResetTasks = () => {
  Object.assign(taskQuery, { title: '', type: '', status: '' })
  taskPagination.pageNum = 1
  loadTasks()
}

const openCreateStudent = () => {
  createStudentVisible.value = true
}
const resetCreateStudentForm = () => {
  createStudentForm.username = ''
  createStudentForm.name = ''
  createStudentForm.email = ''
  createStudentForm.className = ''
}
const submitCreateStudent = async () => {
  try {
    await createStudentFormRef.value?.validate()
    // 先创建基础账号，后补充学生信息
    const created = await createRandomUser('student')
    const userId = created?.userId || created?.data?.userId
    if (!userId) throw new Error('创建学生失败：缺少userId')
    await updateUser(userId, {
      username: createStudentForm.username,
      studentNo: createStudentForm.studentNo,
      realName: createStudentForm.realName,
      gender: createStudentForm.gender,
      email: createStudentForm.email,
      phone: createStudentForm.phone,
      schoolName: createStudentForm.schoolName,
      collegeName: createStudentForm.collegeName,
      majorName: createStudentForm.majorName,
      className: createStudentForm.className,
      grade: createStudentForm.grade,
      avatarUrl: createStudentForm.avatarUrl,
      role: 'student'
    })
    message.success('已创建学生')
    createStudentVisible.value = false
    resetCreateStudentForm()
    await loadStudents()
  } catch (e) {
    // 已有错误提示由 http 拦截器处理
  }
}
const openEditStudent = (row) => {
  editStudentForm.userId = row.userId || row.id
  editStudentForm.username = row.username
  editStudentForm.studentNo = row.studentNo
  editStudentForm.realName = row.realName || row.name
  editStudentForm.gender = row.gender
  editStudentForm.email = row.email
  editStudentForm.phone = row.phone
  editStudentForm.schoolName = row.schoolName
  editStudentForm.collegeName = row.collegeName
  editStudentForm.majorName = row.majorName
  editStudentForm.className = row.className
  editStudentForm.grade = row.grade
  editStudentForm.avatarUrl = row.avatarUrl
  editStudentVisible.value = true
}
const submitEditStudent = async () => {
  try {
    await editStudentFormRef.value?.validate()
    await updateUser(editStudentForm.userId, {
      username: editStudentForm.username,
      studentNo: editStudentForm.studentNo,
      realName: editStudentForm.realName,
      gender: editStudentForm.gender,
      email: editStudentForm.email,
      phone: editStudentForm.phone,
      schoolName: editStudentForm.schoolName,
      collegeName: editStudentForm.collegeName,
      majorName: editStudentForm.majorName,
      className: editStudentForm.className,
      grade: editStudentForm.grade,
      avatarUrl: editStudentForm.avatarUrl
    })
    message.success('已保存学生信息')
    editStudentVisible.value = false
    await loadStudents()
  } catch (_) {}
}
const confirmDeleteStudent = async (row) => {
  try {
    Modal.confirm({
      title: '删除确认',
      content: `确认删除学生「${row.name || row.username}」吗？\n\n删除后将：\n• 移除该学生的所有环境访问权限\n• 删除该学生的所有相关数据\n• 此操作不可恢复！`,
      okText: '删除',
      okType: 'danger',
      cancelText: '取消',
      onOk: async () => {
        try {
          // 显示删除进度
          message.loading('正在删除学生...', 0)
          
          await deleteUser(row.userId || row.id)
          
          // 关闭加载提示
          message.destroy()
          
          message.success('已删除')
          await loadStudents()
        } catch (error) {
          // 关闭加载提示
          message.destroy()
          
          console.error('删除学生失败:', error)
          message.error('删除失败，请重试')
        }
      }
    })
  } catch (error) {
    console.error('显示确认对话框失败:', error)
    message.error('操作失败，请重试')
  }
}

async function loadStudents () {
  try {
    const params = { ...studentQuery, pageNum: studentPagination.pageNum, pageSize: studentPagination.pageSize }
    const page = await pageStudentsApi(params)
    // 统一返回体已在 http 解包，这里拿到的是 PageResult
    students.value = Array.isArray(page?.records) ? page.records : []
    studentPagination.total = page?.total || 0
  } catch (_) {}
}

async function loadTasks () {
  try {
    const data = await pageTasks({ pageNum: taskPagination.pageNum, pageSize: taskPagination.pageSize, ...taskQuery })
    tasks.value = Array.isArray(data?.records) ? data.records : []
    taskPagination.total = data?.total || 0
  } catch (_) {}
}

async function loadEnvs () {
  try {
    const data = await pageTeacherEnvs({ ...envQuery, pageNum: envPage.pageNum, pageSize: envPage.pageSize })
    envs.value = Array.isArray(data?.records) ? data.records : []
    envPage.total = data?.total || 0
  } catch (_) {}
}

onMounted(() => {
  loadTasks()
  loadEnvs()
  loadStudents()
})

// 环境资源 - 学生访问管理
const usageVisible = ref(false)
const currentEnv = ref(null)
const currentUsages = ref([])
const singleUsage = reactive({ studentNo: '', displayName: '', accessUsername: '', accessPassword: '', workDir: '' })
const batchInput = ref('')
const studentPicker = reactive({ selected: [], options: [], loading: false })
const classPicker = reactive({ major: '', className: '', optionsMajor: [], optionsClass: [], loadingMajor: false, loadingClass: false })

// 学生访问数据分页配置
const usagePagination = reactive({
  current: 1,
  pageSize: 10,
  total: 0,
  showSizeChanger: true,
  showQuickJumper: true,
  showTotal: (total, range) => `第 ${range[0]}-${range[1]} 条，共 ${total} 条`,
  pageSizeOptions: ['10', '20', '50', '100'],
  onChange: (page, pageSize) => {
    usagePagination.current = page
    usagePagination.pageSize = pageSize
    loadCurrentUsages()
  },
  onShowSizeChange: (current, size) => {
    usagePagination.current = 1
    usagePagination.pageSize = size
    loadCurrentUsages()
  }
})

// 添加全局loading状态
const usageLoading = reactive({
  addingStudents: false,      // 添加学生中
  addingClassStudents: false, // 添加班级学生中
  refreshing: false           // 刷新列表中
})

async function openManageUsages (env) {
  currentEnv.value = env
  usageVisible.value = true
  
  // 重置分页配置
  usagePagination.current = 1
  usagePagination.pageSize = 10
  usagePagination.total = 0
  
  // 显示初始加载状态
  usageLoading.refreshing = true
  
  try {
    await loadCurrentUsages()
  } catch (error) {
    console.error('加载学生访问列表失败:', error)
    currentUsages.value = []
    message.error('加载学生访问列表失败')
  } finally {
    usageLoading.refreshing = false
  }
}

async function loadCurrentUsages () {
  if (!currentEnv.value) return
  
  try {
    console.log('加载学生访问数据:', {
      environmentId: currentEnv.value.environmentId,
      pageNum: usagePagination.current,
      pageSize: usagePagination.pageSize
    })
    
    const data = await listUsages(currentEnv.value.environmentId, usagePagination.current, usagePagination.pageSize)
    
    console.log('API返回数据:', data)
    
    // 处理分页数据
    if (data && typeof data === 'object' && 'records' in data) {
      // 新的分页API返回格式
      currentUsages.value = Array.isArray(data.records) ? data.records : []
      usagePagination.total = data.total || 0
      console.log('使用分页格式，总数:', usagePagination.total)
    } else {
      // 兼容旧的API返回格式（直接返回数组）
      currentUsages.value = Array.isArray(data) ? data : []
      usagePagination.total = currentUsages.value.length
      console.log('使用兼容格式，总数:', usagePagination.total)
    }
  } catch (error) {
    console.error('加载学生访问列表失败:', error)
    currentUsages.value = []
    usagePagination.total = 0
    message.error('加载学生访问列表失败')
  }
}

async function confirmRemoveEnv (env) {
  console.log('confirmRemoveEnv 被调用，参数:', env) // 调试信息
  
  // 先测试简单的确认对话框
  Modal.confirm({
    title: '确认删除环境资源',
    content: `确定要删除环境资源"${env.name}"吗？\n\n删除后将：\n• 移除所有学生的访问权限\n• 删除所有学生的数据库账户和数据\n• 停止并删除Docker容器实例\n\n此操作不可恢复，请确认！`,
    okText: '确认删除',
    cancelText: '取消',
    okType: 'danger',
    onOk: async () => {
      console.log('用户确认删除')
      try {
        // 显示删除进度
        message.loading('正在删除环境资源和相关资源...', 0)
        
        await removeEnv(env)
        
        // 关闭加载提示
        message.destroy()
        
        // 显示成功消息
        message.success('环境资源删除成功')
        
      } catch (error) {
        // 关闭加载提示
        message.destroy()
        
        console.error('删除失败:', error)
        message.error('删除失败，请重试')
      }
    }
  })
}

async function removeEnv (env) {
  try {
    await deleteTeacherEnv(env.environmentId)
    message.success('环境资源删除成功')
    await loadEnvs()
  } catch (error) {
    console.error('删除环境失败:', error)
    message.error('删除环境失败，请重试')
  }
}

async function confirmRemoveUsage (usage) {
  Modal.confirm({
    title: '移除学生访问确认',
    content: `确定要移除学生"${usage.displayName}"的访问权限吗？\n\n移除后将：\n• 删除该学生的访问记录\n• 删除相关的数据库账户和数据（如果是数据库类型）\n• 删除Jupyter用户目录（如果是Jupyter类型）\n\n此操作不可恢复，请确认！`,
    okText: '确认移除',
    cancelText: '取消',
    okType: 'danger',
    onOk: async () => {
      try {
        message.loading('正在移除学生访问权限和相关资源...', 0)
        
        await deleteUsage(usage.id)
        
        message.destroy()
        message.success('已移除学生访问权限和相关资源')
        
        // 刷新学生访问列表
        await loadCurrentUsages()
        
      } catch (error) {
        message.destroy()
        console.error('删除学生访问失败:', error)
        message.error('删除学生访问失败，请重试')
      }
    }
  })
}

async function addSingleUsage () {
  if (!currentEnv.value) return
  const u = {
    studentNo: singleUsage.studentNo,
    displayName: singleUsage.displayName,
    accessUsername: singleUsage.accessUsername || singleUsage.studentNo,
    accessPassword: singleUsage.accessPassword || '123456',
    workDir: singleUsage.workDir || `/workspace/${singleUsage.studentNo || 'student'}`
  }
  try {
    await bindUsages(currentEnv.value.environmentId, [u])
    message.success('已添加')
    Object.assign(singleUsage, { studentNo: '', displayName: '', accessUsername: '', accessPassword: '', workDir: '' })
    currentUsages.value = await listUsages(currentEnv.value.environmentId)
  } catch (_) {}
}

async function addBatchUsages () {
  if (!currentEnv.value || !batchInput.value) return
  const lines = batchInput.value.split(/\r?\n/).map(s => s.trim()).filter(Boolean)
  const usages = lines.map(line => {
    const [no, name] = line.split(/[,\s]+/)
    return {
      studentNo: no,
      displayName: name || no,
      accessUsername: no,
      accessPassword: no, // 按需作为默认密码
      workDir: `/workspace/${no}`
    }
  })
  try {
    await bindUsages(currentEnv.value.environmentId, usages)
    message.success('已批量添加')
    batchInput.value = ''
    currentUsages.value = await listUsages(currentEnv.value.environmentId)
  } catch (_) {}
}

// 远程搜索学生（支持学号/姓名模糊）
let studentSearchTimer
async function remoteSearchStudents (query) {
  clearTimeout(studentSearchTimer)
  studentSearchTimer = setTimeout(async () => {
    if (!query || query.trim().length < 2) {
      studentPicker.options = []
      return
    }
    
    studentPicker.loading = true
    try {
      const page = await pageStudentsApi({ pageNum: 1, pageSize: 20, realName: query, studentNo: query })
      const records = Array.isArray(page?.records) ? page.records : []
      studentPicker.options = records.map(r => ({
        label: `${r.studentNo || r.username || ''} ${r.realName || r.name || ''}`.trim(),
        value: JSON.stringify({ studentNo: r.studentNo || r.username, displayName: r.realName || r.name })
      }))
    } catch (error) {
      console.error('搜索学生失败:', error)
      studentPicker.options = []
    } finally {
      studentPicker.loading = false
    }
  }, 300) // 增加防抖时间到300ms
}

async function addSelectedStudents () {
  if (!studentPicker.selected.length) {
    message.warning('请先选择学生')
    return
  }
  
  usageLoading.addingStudents = true
  
  try {
    console.log('==========>',studentPicker.selected);
    // 解析选中的学生数据
    const selectedData = studentPicker.selected.map(s => JSON.parse(s))
    console.log('解析后的学生数据:', selectedData)
    
    const usages = studentPicker.selected.map(s => JSON.parse(s))
    
    await bindUsages(currentEnv.value.environmentId, usages)
    
    message.success(`已成功添加 ${usages.length} 名学生访问权限`)
    
    // 清空选择
    studentPicker.selected = []
    
    // 刷新学生访问列表
    await loadCurrentUsages()
    
  } catch (error) {
    console.error('添加学生访问失败:', error)
    message.error('添加学生访问失败，请重试')
  } finally {
    usageLoading.addingStudents = false
  }
}

// 远程加载专业/班级
let majorSearchTimer
async function remoteSearchMajor (q) {
  clearTimeout(majorSearchTimer)
  majorSearchTimer = setTimeout(async () => {
    if (!q || q.trim().length < 2) {
      classPicker.optionsMajor = []
      return
    }
    
    classPicker.loadingMajor = true
    try {
      const arr = await listStudentMajors(q)
      classPicker.optionsMajor = (arr || []).map(m => ({ label: m, value: m }))
    } catch (error) {
      console.error('搜索专业失败:', error)
      classPicker.optionsMajor = []
    } finally { 
      classPicker.loadingMajor = false 
    }
  }, 300) // 增加防抖时间到300ms
}

function onMajorChange () {
  classPicker.className = ''
  classPicker.optionsClass = []
}

let classSearchTimer
async function remoteSearchClass (q) {
  clearTimeout(classSearchTimer)
  classSearchTimer = setTimeout(async () => {
    if (!q || q.trim().length < 2) {
      classPicker.optionsClass = []
      return
    }
    
    classPicker.loadingClass = true
    try {
      const arr = await listStudentClasses({ like: q, majorName: classPicker.major })
      classPicker.optionsClass = (arr || []).map(c => ({ label: c, value: c }))
    } catch (error) {
      console.error('搜索班级失败:', error)
      classPicker.optionsClass = []
    } finally { 
      classPicker.loadingClass = false 
    }
  }, 300) // 增加防抖时间到300ms
}

async function addClassStudents () {
  if (!classPicker.major || !classPicker.className) {
    message.warning('请先选择专业和班级')
    return
  }
  
  usageLoading.addingClassStudents = true
  
  try {
    // 根据专业和班级获取学生列表
    const page = await pageStudentsApi({ 
      pageNum: 1, 
      pageSize: 1000, 
      className: classPicker.className, 
      majorName: classPicker.major 
    })
    
    const students = Array.isArray(page?.records) ? page.records : []
    
    if (!students.length) {
      message.warning('该班级暂无学生')
      return
    }
    
    const usages = students.map(student => ({
      studentNo: student.username,
      displayName: student.username
    }))
    
    await bindUsages(currentEnv.value.environmentId, usages)
    
    message.success(`已成功添加 ${usages.length} 名班级学生访问权限`)
    
    // 清空选择
    classPicker.major = ''
    classPicker.className = ''
    
    // 刷新学生访问列表
    await loadCurrentUsages()
    
  } catch (error) {
    console.error('添加班级学生访问失败:', error)
    message.error('添加班级学生访问失败，请重试')
  } finally {
    usageLoading.addingClassStudents = false
  }
}

// 辅助显示
const statusLabel = (s) => ({ pending: '待发布', 'in-progress': '进行中', completed: '已完成' }[s] || s)
const statusTagColor = (s) => ({ pending: 'blue', 'in-progress': 'orange', completed: 'green' }[s] || 'blue')
const typeLabel = (t) => ({ coding: '编程', quiz: '测验', project: '项目', reading: '阅读' }[t] || t)
const difficultyLabel = (d) => ({ easy: '简单', medium: '中等', hard: '困难' }[d] || d)
const envStatusLabel = (s) => ({ ready: '就绪', creating: '创建中', error: '异常' }[s] || s)
const envTagColor = (s) => ({ ready: 'green', creating: 'orange', error: 'red', running: 'green' }[s] || 'blue')
const formatDate = (str) => new Date(str).toLocaleDateString('zh-CN')

// 退出登录
function handleLogout () {
  try { doLogout() } catch {}
  message.success('已退出')
  router.replace('/login')
}
</script>

<style scoped>
.teacher-center {
  position: relative;
  z-index: 1;
  padding: 24px;
  margin: 0 auto;
}

.fullscreen-bg {
  position: fixed;
  inset: 0;
  background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
  z-index: -1;
  pointer-events: none;
}

.page-header {
  text-align: left;
  color: #fff;
  margin-bottom: 24px;
  position: relative;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
}

.welcome { opacity: 0.95; margin: 4px 0; font-weight: 600; }

.page-header h1 {
  font-size: 2.2rem;
  margin: 0 0 8px 0;
}

.subtitle { opacity: 0.9; }

.page-actions {
  position: absolute;
  top: 0;
  right: 0;
}

.tabs :deep(.ant-tabs-nav) { margin-bottom: 16px; }
.tabs :deep(.ant-tabs-nav)::before { border-bottom: 0; }
.tabs :deep(.ant-tabs-ink-bar) { height: 3px; background: linear-gradient(90deg, #667eea, #764ba2); }
.tabs :deep(.ant-tabs-tab .ant-tabs-tab-btn) { font-weight: 600; color: rgba(255,255,255,0.85); }
.tabs :deep(.ant-tabs-tab-active .ant-tabs-tab-btn) { color: #fff; }
.tabs :deep(.ant-tabs-content-holder) {
  height: 100%;
  background: rgba(255, 255, 255, 0.92);
  backdrop-filter: blur(10px);
  border-radius: 16px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.12);
  padding: 16px;
}

.toolbar {
  display: flex;
  justify-content: flex-end;
  margin-bottom: 16px;
  position: sticky;
  top: 12px;
  z-index: 2;
}
.toolbar :deep(.ant-btn-primary) { box-shadow: 0 8px 20px rgba(102, 126, 234, 0.35); }

.filter-row {
  margin-bottom: 12px;
}

.card-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 20px;
  align-items: stretch;
}

.card {
  background: rgba(255, 255, 255, 0.96);
  border-radius: 16px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.12);
  padding: 18px 16px 16px;
  border: 1px solid rgba(255, 255, 255, 0.35);
  position: relative;
  transition: transform .25s ease, box-shadow .25s ease;
}
.card::before { display: none; }
.card:hover {
  transform: translateY(-6px);
  box-shadow: 0 18px 42px rgba(0, 0, 0, 0.18);
}

.card-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 12px;
}

.title {
  font-weight: 700;
  color: #2c3e50;
  font-size: 1.05rem;
  letter-spacing: 0.2px;
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}

.card-content .meta {
  display: grid;
  gap: 8px 16px;
  background: #f3f5f7;
  padding: 12px;
  border-radius: 10px;
}

.meta-item { display: flex; justify-content: space-between; color: #5a6c7d; }
.meta-item strong { color: #2c3e50; }
.monospace {
  font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;
  word-break: break-all;
  overflow-wrap: anywhere;
  width: 80%;
  display: inline-block;
  text-align: right;
  margin-left: auto;
}

.desc {
  color: #5a6c7d;
  margin-top: 12px;
  line-height: 1.65;
}

/* 分页样式优化 */
.ant-table-pagination {
  margin-top: 16px;
  text-align: right;
}

/* 表格样式优化 */
.ant-table {
  background: rgba(255, 255, 255, 0.96);
  border-radius: 12px;
  overflow: hidden;
  box-shadow: 0 4px 20px rgba(0, 0, 0, 0.08);
}

.ant-table-thead > tr > th {
  background: #f8f9fa;
  border-bottom: 1px solid #e8e8e8;
  font-weight: 600;
  color: #2c3e50;
}

.ant-table-tbody > tr > td {
  border-bottom: 1px solid #f0f0f0;
  padding: 12px 16px;
}

.ant-table-tbody > tr:hover > td {
  background: #f8f9fa;
}

.ant-table-tbody > tr:last-child > td {
  border-bottom: none;
}

.ant-table-pagination .ant-pagination-total {
  color: #5a6c7d;
  font-weight: 500;
}

.ant-table-pagination .ant-pagination-item {
  border-radius: 8px;
  border: 1px solid #d9d9d9;
  transition: all 0.2s ease;
}

.ant-table-pagination .ant-pagination-item:hover {
  border-color: #667eea;
  color: #667eea;
}

.ant-table-pagination .ant-pagination-item-active {
  background: #667eea;
  border-color: #667eea;
}

.ant-table-pagination .ant-pagination-item-active a {
  color: #fff;
}

.ant-table-pagination .ant-pagination-options {
  margin-left: 16px;
}

.ant-table-pagination .ant-select {
  border-radius: 8px;
}

.ant-table-pagination .ant-pagination-options-quick-jumper {
  margin-left: 16px;
}

.ant-table-pagination .ant-pagination-options-quick-jumper input {
  border-radius: 6px;
  border: 1px solid #d9d9d9;
  transition: border-color 0.2s ease;
}

.ant-table-pagination .ant-pagination-options-quick-jumper input:focus {
  border-color: #667eea;
  box-shadow: 0 0 0 2px rgba(102, 126, 234, 0.2);
}

@media (max-width: 768px) {
  .tabs :deep(.el-tabs__content) { padding: 12px; border-radius: 12px; }
  .card-grid { grid-template-columns: 1fr; gap: 14px; }
}
</style>